import java.util.Random;
import java.util.Timer;
import java.util.TimerTask;
//import javax.swing.Timer;
public class TimmerDemo {
    protected static Timer reapeatTimer() {
        Timer timer = new Timer();
        Random intRand = new Random();
        // schedule在制定反复执行一个task的计划时，每一次执行这个task的计划执行时间随着前一次的实际执行时间而变，
        // 也就是 scheduledExecutionTime(第n+1次)=realExecutionTime(第n次)+periodTime。
        // 也就是说如果第n 次执行task时，由于某种原因这次执行时间过长，执行完后的systemCurrentTime>= scheduledExecutionTime(第n+1次)，则此时不做时隔等待，立即执行第n+1次task，
        // 而接下来的第n+2次task的 scheduledExecutionTime(第n+2次)就随着变成了realExecutionTime(第n+1次)+periodTime。
        // 说白了，这个方法更注重保持间隔时间的稳定。
        timer.schedule(new TimerTask() {
            int callCount = 0;
            @Override
            public void run() {
                ++ callCount;
                if (callCount > 20) {
                    timer.cancel();
                    return;
                }
                int sleepMS = intRand.nextInt(201);
                DateTimeDemo.logTs(callCount + ", fixDelay 100ms 执行, sleep "+sleepMS);
                try {
                    Thread.sleep(sleepMS);
                } catch (InterruptedException e) {
                    throw new RuntimeException(e);
                }
            }
        }, 500, 100);

        try {
            Thread.sleep(200);
        } catch (InterruptedException e) {
            throw new RuntimeException(e);
        }

        return timer;
    }

    protected static Timer reapeatTimer2() {
        Random intRand = new Random();
        Timer timer2 = new Timer();
        // 500 ms 后, 按 100ms 间隔执行task，但是task如果没在100ms执行完，后面的task立马执行

        // scheduleAtFixedRate在制定反复执行一个task的计划时，每一次 执行这个task的计划执行时间在最初就被定下来了，
        // 也就是scheduledExecutionTime(第n次)=firstExecuteTime +n*periodTime；
        // 如果第n次执行task时，由于某种原因这次执行时间过长，执行完后的systemCurrentTime>= scheduledExecutionTime(第n+1次)，则此时不做period间隔等待，立即执行第n+1次task，
        // 而接下来的第n+2次的 task的scheduledExecutionTime(第n+2次)依然还是firstExecuteTime+（n+2)*periodTime这 在第一次执行task就定下来了。
        // 说白了，这个方法更注重保持执行频率的稳定
        timer2.scheduleAtFixedRate (new TimerTask() {
            int callCount = 0;
            @Override
            public void run() {
                ++ callCount;
                if (callCount > 20) {
                    timer2.cancel();
                    return;
                }
                int sleepMS = intRand.nextInt(201);
                DateTimeDemo.logTs(callCount + ", AtFixedRate 100ms 执行, sleep "+sleepMS);
                try {
                    Thread.sleep(sleepMS);
                } catch (InterruptedException e) {
                    throw new RuntimeException(e);
                }
            }
        }, 500, 100);
        return timer2;
    }


    protected static void demoLogic() {
        DateTimeDemo.logTs("reapeatTimer");
        Timer tm = reapeatTimer();

        // 基于 java.util.Timer 的延时执行
        tm.schedule(new TimerTask() {
            @Override
            public void run() {
                DateTimeDemo.logTs("2000ms 后 执行 tm.cancel");
                //tm.cancel();
            }
        }, 2000);

        // 基于 javax.swing.Timer 的延时执行
        javax.swing.Timer stm = new javax.swing.Timer(2500, event -> {
            DateTimeDemo.logTs("javax.swing.Timer, event:" + event);
            TimmerDemo.reapeatTimer2();

        });
        stm.setRepeats(false);
        stm.start();
    }
}
